package com.haoqizhe.kernel.shiro.jwt;

import com.haoqizhe.kernel.jwt.utils.JwtTokenUtil;
import com.haoqizhe.kernel.commons.util.IpUtil;
import io.jsonwebtoken.Claims;
import lombok.Data;
import lombok.experimental.Accessors;
import org.apache.shiro.authc.HostAuthenticationToken;

import java.util.Date;
import java.util.HashMap;
import java.util.Map;

/**
 * shiro jwt token
 *
 * @author haoqizhe.li
 * @date 2021/01/25 19:52
 */
@Data
@Accessors(chain = true)
public class JwtToken implements HostAuthenticationToken {

    public static final String SALT = "SALT";

    public static final String USER_ID = "USER_ID";

    // 登陆设备
    public static final String DEVICE = "DEVICE";

    /**
     * 登录ip
     */
    private String host;
    /**
     * 登录用户名称
     */
    private String username;
    /**
     * 登录盐值
     */
    private String salt;
    /**
     * 登录token
     */
    private String token;
    /**
     * 创建时间
     */
    private Date createDate;
    /**
     * 多长时间过期，默认一小时
     */
    private long expireSecond;
    /**
     * 过期日期
     */
    private Date expireDate;

    private String principal;

    private String credentials;

    /**
     * 登陆设备
     */
    private String device;

    private Object userId;

    private boolean rememberMe;

    @Override
    public Object getPrincipal() {
        return token;
    }

    @Override
    public Object getCredentials() {
        return token;
    }

    public static String createToken(String username, Object userId, String salt, String device, Map<String, Object> map, boolean rememberMe, JwtTokenUtil jwtTokenUtil) {

        if (map == null) {
            map = new HashMap<>(0);
        }
        map.put(SALT, salt);
        map.put(USER_ID, userId);
        map.put(DEVICE, device);

        return jwtTokenUtil.createToken(username, map, rememberMe);
    }

    public static JwtToken build(String token, JwtTokenUtil jwtTokenUtil) {

        Claims claims = jwtTokenUtil.getClaimsFromToken(token);

        return new JwtToken()
                .setUsername(claims.getSubject())
                .setToken(token)
                .setHost(IpUtil.getServiceIp())
                .setSalt(String.valueOf(claims.get(SALT)))
                .setUserId(claims.get(USER_ID))
                .setDevice(String.valueOf(claims.get(DEVICE)))
                .setCreateDate(claims.getIssuedAt())
                .setExpireSecond(jwtTokenUtil.expireSecond())
                .setExpireDate(claims.getExpiration())
                .setRememberMe(jwtTokenUtil.getRememberMe(token));
    }
}
